/*********************************************************************************
 *      Copyright:  (C) 2023 iot<iot@email.com>
 *                  All rights reserved.
 *
 *       Filename:  main.c
 *    Description:  This file 
 *                 
 *        Version:  1.0.0(04/11/23)
 *         Author:  iot <iot@email.com>
 *      ChangeLog:  1, Release initial version on "04/11/23 15:16:30"
 *                 
 ********************************************************************************/
#include <stdio.h>
#include <dirent.h>
#include <string.h>
#include <sys/types.h>
#include <sys/stat.h>
#include <fcntl.h>
#include <unistd.h>
#include <stdlib.h>
#include <errno.h>
#include <sys/time.h>
#include <sys/types.h>
#include <sys/socket.h>
#include <unistd.h>
#include <arpa/inet.h>
#include <string.h>
#include <getopt.h>
#include <time.h>
#include <sqlite3.h>
#include <signal.h>
#include <libgen.h>
#include <linux/tcp.h>
#include <netinet/in.h>
#include <netinet/ip.h>
#include <netdb.h>

#include "sql_client.h"
#include "get_data.h"
#include "data_process.h"
#include "logger.h"
#include "socket.h"


static inline void print_usage(char *progname);
void sig_handle(int signum);

int		g_stop = 0;

int main(int argc,char **argv)
{
	sample_data_t   				sample_data;
    socket_t                        socket;
	struct timeval					tv;
	long							current_time;
	long							pre_time = 0;
	int								send_time = 5;
	char							buf[128];
	char							buf_db[128];
	int								rv;
	int								sample=0;
	char							*hostname = NULL;
	int								port = 0;
	int								ch;
	int								daemon_run = 0;
	int								t = 0;
    int                             bytes = -1;
	char							*p = NULL;
	char							db_name[32] = "sql_temp_ser.db";
	
	struct option           opts[]={
                                        {"hostname",required_argument,NULL,'h'},
                                        {"port",required_argument,NULL,'p'},
                                        {"help",no_argument,NULL,'H'},
										{"daemon", no_argument, NULL, 'b'},
										{"send",required_argument,NULL,'t'},
                                        {0,0,0,0}
                                    };

	while( (ch=getopt_long(argc,argv,"h:p:t:bH",opts,NULL))!=-1)
    {
        switch(ch)
        {
            case 'h':
					hostname = (optarg);
                    break;


            case 'p':
                     port = atoi(optarg);
                     break;

			case 't':
					 send_time = atoi(optarg);
					 break;

			case 'b':
					 daemon_run = 1;
					 break;

            case 'H':
                      print_usage(argv[0]);
					  break;
        }
    }

	if( !socket.hostname )
    {
        print_usage(argv[0]);
        return -1;
    }



	if (logger_init("stdout", LOG_LEVEL_DEBUG) < 0)
	{
		fprintf(stderr,"initial logger system failure\n");
		return -2;
	}


	signal(SIGINT,sig_handle);
	signal(SIGTERM,sig_handle);

	if( daemon_run )
	{
		if( daemon(1,0) )
		{
			log_error("Running daemon failure:%s\n", strerror(errno));
		}
		else
		{
			if( logger_init("client.log", LOG_LEVEL_DEBUG) < 0)
			{
				fprintf(stderr, "initial logger system failure\n");
				return -2;
			}
			log_info("Running daemon successfully\n");
		}
	}

	if( (socket_init(&socket,&hostname,port)) != 0 )
	{
		 log_warning("socket first initialization failed\n");
	}
	else
	{
		log_info("socket first initialization scuessfully\n");
	}

	if( creat_db(db_name) < 0 )
    {
        log_warning("creat database failure\n");
        return -3;
    }

	while( !g_stop )
	{
		sample = 0;

		gettimeofday(&tv, NULL);
		current_time=tv.tv_sec;

		if( (current_time-pre_time) >= send_time )
		{
			if( (rv=sample_package(&sample_data)) < 0 )
			{
				log_warning("data acquisition error");
				return -4;
			}
			log_info("buf:%s,buf_length:%d\n",buf,rv);
			
			sample = 1;
			pre_time = current_time;
		}
		
		if( socket_state(socket) < 0 )
        {
            if( (socket.socketfd = socket_connect(&socket)) < 0 )
            {
				log_warning("reconnect to server failure:%s\n",strerror(errno));
            }
            else
            {
				log_info("connect to server successful.\n");
            }
         }
		
		if( !socket.status  )
		{
			if(sample)
			{
				if( insert_db(sample_data) < 0)
				{
					log_warning("message insert database failure\n");
					close_db();
					return -4;
				}
			}
			continue;
		}
		
		if( sample )
		{
			 if( 0 == send_package(socket,sample_data) )
			 {
				 log_info("send the data ok\n");
			 }
			 else
			 {
				 log_warning("send the data failure,insert_db\n");

				 if( insert_db(sample_data) < 0)
				 {
					 log_warning("message insert database failure\n");
					 close_db();
					 return -4;
				 }
				
				 socket_close(&socket);
			 }
		}

		if( (bytes = select_db(&sample_data) ) > 0)
		{
			if( send_package(socket,sample_data) < 0 )
			{
				socket_close(&socket);
			}
			else
			{
				if( delete_db( getrow_db() ) < 0 )
				{
					log_warning("delete_db failure\n");
					close_db();
					return -5;
				}
			}
		}/* if( (max_row = getrow_db() ) > 0) */

	}/* while( !g_stop )*/
}

void print_usage(char *program)
{
    printf("%s usage:\n",program);
    printf("-h(--hostname):sepcify serve hostname\n");
    printf("-p(--port):sepcify serve port\n");
    printf("-H(--help):printf this help information\n");
	printf("-b[daemon]:Start daemon!\n");
	printf("-t(--second):specify second\n");
}

void sig_handle(int signum)
{
    log_warning("catch signal [%d]\n",signum);
		
	g_stop  = 1;
}
